﻿/*
   HeyGov! 311
   Copyright © 2011 – ISC. All Rights Reserved.
*/

using System;
using System.Configuration;
using System.IO;
using System.Net;
using System.Web;
using System.Web.SessionState;



namespace OI.Web.Apps
{
    public class Redirect : IHttpHandler, IReadOnlySessionState 
    {
        #region ERROR_CODES
        public static int ErrIDNotProvided = 412;
        public static int ErrIDNotFound = 404;
        public static int ErrGeneral = 400;
        #endregion


        public void ProcessRequest(HttpContext context)
        {
            try
            {
                // querystring and form parts of incoming request
                var queryStringArray = HttpContext.Current.Request.QueryString;

                // get the root of the path to the location where apps are stored
                // this is a fully qualified path
                string appsRoot = ConfigurationManager.AppSettings["AppsRoot"].Trim('/');

                // get the rest of the path from this context (everything after /Apps)
                int idx = context.Request.Path.IndexOf("Apps/", StringComparison.CurrentCultureIgnoreCase) + 5;
                string path = context.Request.Path.Substring(idx);

                // construct the redirect url
                string url = appsRoot + "/" + path + (queryStringArray.Count > 0 ? "?" + queryStringArray : "");

                // handle redirect
                HttpRequest original = context.Request; 

                // set the redirect request to be like the original
                var newRequest = (HttpWebRequest)WebRequest.Create(url); 
                newRequest.ContentType = original.ContentType; 
                newRequest.Method = original.HttpMethod;
                newRequest.UserAgent = original.UserAgent;

                // write the response from the redirected request
                var wr = newRequest.GetResponse();
                var rs = wr.GetResponseStream();
                if (rs != null)
                {
                    var bytes = Read(rs, (int)wr.ContentLength);
                    context.Response.ContentType = wr.ContentType;
                    context.Response.BinaryWrite(bytes);
                }
            }
            catch (Exception ex)
            {
                context.Response.Write(ex.Message);
            }
        }
        

        private byte[] Read(Stream stream, int contentLength)
        {
            const int buffSize = 1024;
            if (stream != null)
            {
                using (var br = new BinaryReader(stream))
                {
                    int loops = contentLength / buffSize;
                    if (contentLength > 0)
                    {
                        using (var ms = new MemoryStream())
                        {
                            for (int i = 0; i < loops; i++)
                            {
                                ms.Write(br.ReadBytes(buffSize), 0, buffSize);
                            }
                            int remSize = contentLength - (loops * buffSize);
                            ms.Write(br.ReadBytes(remSize), 0, remSize);
                            return ms.ToArray();
                        }
                    }
                }
            }
            return null;
        }


        public bool IsReusable
        {
            get
            {
                return false;
            }
        }
    }
}